/**
 * XappTool Android Native SDK
 * 免邀请安装归因 SDK
 * 类似 xinstall/openinstall/sharetrace 功能
 * @version 1.0.0
 */

package com.xapptool.sdk;

import android.content.Context;
import android.content.SharedPreferences;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.os.Build;
import android.provider.Settings;
import android.telephony.TelephonyManager;
import android.util.DisplayMetrics;
import android.view.Display;
import android.view.WindowManager;

import org.json.JSONException;
import org.json.JSONObject;

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;

public class XappToolAndroid {
    
    private static final String TAG = "XappTool";
    private static final String SDK_VERSION = "1.0.0";
    private static final String API_BASE_URL = "https://api.xapptool.cn";
    private static final String PREFS_NAME = "xapptool_prefs";
    private static final String KEY_DEVICE_FINGERPRINT = "device_fingerprint";
    private static final String KEY_SESSION_ID = "session_id";
    
    private Context context;
    private SharedPreferences prefs;
    private ExecutorService executor;
    private XappToolConfig config;
    private boolean isInitialized = false;
    private String deviceFingerprint;
    private String sessionId;
    private DeviceInfo deviceInfo;
    
    // 配置类
    public static class XappToolConfig {
        private String apiKey;
        private String apiUrl = API_BASE_URL;
        private int timeout = 5000;
        private boolean debug = false;
        private String environment = "production";
        private boolean enableCache = true;
        private long cacheTimeout = 3600000;
        private boolean enableCompression = true;
        private boolean batchRequests = false;
        private int batchSize = 10;
        private long batchInterval = 5000;
        
        public XappToolConfig setApiKey(String apiKey) {
            this.apiKey = apiKey;
            return this;
        }
        
        public XappToolConfig setApiUrl(String apiUrl) {
            this.apiUrl = apiUrl;
            return this;
        }
        
        public XappToolConfig setTimeout(int timeout) {
            this.timeout = timeout;
            return this;
        }
        
        public XappToolConfig setDebug(boolean debug) {
            this.debug = debug;
            return this;
        }
        
        public XappToolConfig setEnvironment(String environment) {
            this.environment = environment;
            return this;
        }
        
        public XappToolConfig setEnableCache(boolean enableCache) {
            this.enableCache = enableCache;
            return this;
        }
        
        public XappToolConfig setCacheTimeout(long cacheTimeout) {
            this.cacheTimeout = cacheTimeout;
            return this;
        }
        
        public XappToolConfig setEnableCompression(boolean enableCompression) {
            this.enableCompression = enableCompression;
            return this;
        }
        
        public XappToolConfig setBatchRequests(boolean batchRequests) {
            this.batchRequests = batchRequests;
            return this;
        }
        
        public XappToolConfig setBatchSize(int batchSize) {
            this.batchSize = batchSize;
            return this;
        }
        
        public XappToolConfig setBatchInterval(long batchInterval) {
            this.batchInterval = batchInterval;
            return this;
        }
    }
    
    // 设备信息类
    public static class DeviceInfo {
        public String brand;
        public String model;
        public String device;
        public String product;
        public String manufacturer;
        public String androidVersion;
        public int sdkVersion;
        public String screenResolution;
        public int screenWidth;
        public int screenHeight;
        public float density;
        public String language;
        public String country;
        public String timezone;
        public String deviceId;
        public String packageName;
        public String appVersion;
        public String appName;
        public boolean isEmulator;
        public boolean isRooted;
        
        public JSONObject toJSON() throws JSONException {
            JSONObject json = new JSONObject();
            json.put("brand", brand);
            json.put("model", model);
            json.put("device", device);
            json.put("product", product);
            json.put("manufacturer", manufacturer);
            json.put("androidVersion", androidVersion);
            json.put("sdkVersion", sdkVersion);
            json.put("screenResolution", screenResolution);
            json.put("screenWidth", screenWidth);
            json.put("screenHeight", screenHeight);
            json.put("density", density);
            json.put("language", language);
            json.put("country", country);
            json.put("timezone", timezone);
            json.put("deviceId", deviceId);
            json.put("packageName", packageName);
            json.put("appVersion", appVersion);
            json.put("appName", appName);
            json.put("isEmulator", isEmulator);
            json.put("isRooted", isRooted);
            return json;
        }
    }
    
    // 安装参数类
    public static class InstallParams {
        public String inviter;
        public String channel;
        public Map<String, String> params;
        public String attributionType;
        public double confidence;
        public long timestamp;
        
        public InstallParams() {
            this.params = new HashMap<>();
            this.attributionType = "organic";
            this.confidence = 0.0;
            this.timestamp = System.currentTimeMillis();
        }
        
        public JSONObject toJSON() throws JSONException {
            JSONObject json = new JSONObject();
            json.put("inviter", inviter);
            json.put("channel", channel);
            
            JSONObject paramsJSON = new JSONObject();
            for (Map.Entry<String, String> entry : params.entrySet()) {
                paramsJSON.put(entry.getKey(), entry.getValue());
            }
            json.put("params", paramsJSON);
            
            json.put("attributionType", attributionType);
            json.put("confidence", confidence);
            json.put("timestamp", timestamp);
            return json;
        }
    }
    
    // 回调接口
    public interface XappToolCallback<T> {
        void onSuccess(T result);
        void onError(String error);
    }
    
    // 构造函数
    public XappToolAndroid(Context context, XappToolConfig config) {
        this.context = context.getApplicationContext();
        this.config = config;
        this.prefs = context.getSharedPreferences(PREFS_NAME, Context.MODE_PRIVATE);
        this.executor = Executors.newCachedThreadPool();
        
        // 获取设备信息
        this.deviceInfo = getDeviceInfo();
        
        // 生成或获取设备指纹
        this.deviceFingerprint = prefs.getString(KEY_DEVICE_FINGERPRINT, "");
        if (deviceFingerprint.isEmpty()) {
            this.deviceFingerprint = generateDeviceFingerprint();
            prefs.edit().putString(KEY_DEVICE_FINGERPRINT, deviceFingerprint).apply();
        }
        
        // 生成会话ID
        this.sessionId = generateUUID();
    }
    
    /**
     * 初始化 SDK
     */
    public void init(final XappToolCallback<Void> callback) {
        executor.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    if (config.apiKey == null || config.apiKey.isEmpty()) {
                        throw new Exception("API Key is required");
                    }
                    
                    log("Initializing XappTool Android SDK...");
                    
                    // 检查设备是否有效
                    if (deviceInfo.isEmulator || deviceInfo.isRooted) {
                        log("Warning: Running on emulator or rooted device");
                    }
                    
                    isInitialized = true;
                    log("XappTool Android SDK initialized successfully");
                    
                    if (callback != null) {
                        callback.onSuccess(null);
                    }
                    
                } catch (Exception e) {
                    log("SDK initialization failed: " + e.getMessage());
                    if (callback != null) {
                        callback.onError(e.getMessage());
                    }
                }
            }
        });
    }
    
    /**
     * 获取安装参数
     */
    public void getInstallParams(final XappToolCallback<InstallParams> callback) {
        executor.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    if (!isInitialized) {
                        throw new Exception("SDK not initialized");
                    }
                    
                    // 检查缓存
                    if (config.enableCache) {
                        String cached = getCache("install_params_" + deviceFingerprint);
                        if (cached != null) {
                            InstallParams params = parseInstallParams(cached);
                            if (callback != null) {
                                callback.onSuccess(params);
                            }
                            return;
                        }
                    }
                    
                    // 构建请求数据
                    JSONObject requestData = new JSONObject();
                    requestData.put("apiKey", config.apiKey);
                    requestData.put("deviceFingerprint", deviceFingerprint);
                    requestData.put("sessionId", sessionId);
                    requestData.put("deviceInfo", deviceInfo.toJSON());
                    requestData.put("timestamp", System.currentTimeMillis());
                    
                    // 发送归因请求
                    String response = sendRequest("/api/v1/attribution", requestData);
                    JSONObject jsonResponse = new JSONObject(response);
                    
                    if (jsonResponse.getInt("code") != 0) {
                        throw new Exception(jsonResponse.getString("message"));
                    }
                    
                    JSONObject data = jsonResponse.getJSONObject("data");
                    InstallParams params = new InstallParams();
                    params.inviter = data.optString("inviter", null);
                    params.channel = data.optString("channel", null);
                    params.attributionType = data.optString("attributionType", "organic");
                    params.confidence = data.optDouble("confidence", 0.0);
                    params.timestamp = data.optLong("timestamp", System.currentTimeMillis());
                    
                    // 解析参数
                    JSONObject paramsJSON = data.optJSONObject("params");
                    if (paramsJSON != null) {
                        params.params = jsonToMap(paramsJSON);
                    }
                    
                    // 缓存结果
                    if (config.enableCache) {
                        setCache("install_params_" + deviceFingerprint, params.toJSON().toString(), config.cacheTimeout);
                    }
                    
                    if (callback != null) {
                        callback.onSuccess(params);
                    }
                    
                } catch (Exception e) {
                    log("Failed to get install params: " + e.getMessage());
                    
                    // 返回默认参数
                    InstallParams params = new InstallParams();
                    if (callback != null) {
                        callback.onSuccess(params);
                    }
                }
            }
        });
    }
    
    /**
     * 生成邀请链接
     */
    public void generateInvitationLink(final Map<String, Object> options, final XappToolCallback<String> callback) {
        executor.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    if (!isInitialized) {
                        throw new Exception("SDK not initialized");
                    }
                    
                    String userId = (String) options.getOrDefault("userId", "");
                    String code = (String) options.getOrDefault("code", "");
                    String channel = (String) options.getOrDefault("channel", "direct");
                    Map<String, String> params = (Map<String, String>) options.getOrDefault("params", new HashMap<>());
                    int expireDays = (int) options.getOrDefault("expireDays", 7);
                    
                    if (code.isEmpty()) {
                        code = generateUUID().substring(0, 8);
                    }
                    
                    // 构建请求数据
                    JSONObject requestData = new JSONObject();
                    requestData.put("apiKey", config.apiKey);
                    requestData.put("userId", userId);
                    requestData.put("code", code);
                    requestData.put("channel", channel);
                    requestData.put("expireDays", expireDays);
                    requestData.put("deviceFingerprint", deviceFingerprint);
                    requestData.put("deviceInfo", deviceInfo.toJSON());
                    
                    // 添加参数
                    JSONObject paramsJSON = new JSONObject();
                    for (Map.Entry<String, String> entry : params.entrySet()) {
                        paramsJSON.put(entry.getKey(), entry.getValue());
                    }
                    requestData.put("params", paramsJSON);
                    
                    // 发送请求
                    String response = sendRequest("/api/v1/invitation-link", requestData);
                    JSONObject jsonResponse = new JSONObject(response);
                    
                    if (jsonResponse.getInt("code") != 0) {
                        throw new Exception(jsonResponse.getString("message"));
                    }
                    
                    String invitationLink = jsonResponse.getJSONObject("data").getString("invitationLink");
                    
                    if (callback != null) {
                        callback.onSuccess(invitationLink);
                    }
                    
                } catch (Exception e) {
                    log("Failed to generate invitation link: " + e.getMessage());
                    
                    // 生成默认链接
                    String userId = (String) options.getOrDefault("userId", "");
                    String code = (String) options.getOrDefault("code", generateUUID().substring(0, 8));
                    String channel = (String) options.getOrDefault("channel", "direct");
                    
                    StringBuilder linkBuilder = new StringBuilder("https://xapptool.cn/invite?");
                    linkBuilder.append("userId=").append(URLEncoder.encode(userId, "UTF-8"));
                    linkBuilder.append("&code=").append(URLEncoder.encode(code, "UTF-8"));
                    linkBuilder.append("&channel=").append(URLEncoder.encode(channel, "UTF-8"));
                    
                    if (callback != null) {
                        callback.onSuccess(linkBuilder.toString());
                    }
                }
            }
        });
    }
    
    /**
     * 获取设备指纹
     */
    public String getDeviceFingerprint() {
        return deviceFingerprint;
    }
    
    /**
     * 获取设备信息
     */
    public DeviceInfo getDeviceInfo() {
        return deviceInfo;
    }
    
    /**
     * 反作弊检测
     */
    public void checkAntiFraud(final XappToolCallback<JSONObject> callback) {
        executor.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    JSONObject results = new JSONObject();
                    results.put("isSuspicious", false);
                    results.put("reasons", new org.json.JSONArray());
                    results.put("isEmulator", deviceInfo.isEmulator);
                    results.put("isRooted", deviceInfo.isRooted);
                    results.put("deviceInfo", deviceInfo.toJSON());
                    
                    org.json.JSONArray reasons = results.getJSONArray("reasons");
                    
                    // 综合判断
                    if (deviceInfo.isEmulator) {
                        results.put("isSuspicious", true);
                        reasons.put("Detected emulator environment");
                    }
                    
                    if (deviceInfo.isRooted) {
                        results.put("isSuspicious", true);
                        reasons.put("Detected rooted device");
                    }
                    
                    if (callback != null) {
                        callback.onSuccess(results);
                    }
                    
                } catch (Exception e) {
                    log("Anti-fraud check failed: " + e.getMessage());
                    if (callback != null) {
                        callback.onError(e.getMessage());
                    }
                }
            }
        });
    }
    
    /**
     * 获取渠道统计
     */
    public void getChannelStats(final Map<String, Object> options, final XappToolCallback<JSONObject> callback) {
        executor.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    if (!isInitialized) {
                        throw new Exception("SDK not initialized");
                    }
                    
                    String startDate = (String) options.getOrDefault("startDate", getDefaultStartDate());
                    String endDate = (String) options.getOrDefault("endDate", getDefaultEndDate());
                    String channel = (String) options.getOrDefault("channel", "");
                    
                    // 构建请求数据
                    JSONObject requestData = new JSONObject();
                    requestData.put("apiKey", config.apiKey);
                    requestData.put("startDate", startDate);
                    requestData.put("endDate", endDate);
                    requestData.put("channel", channel);
                    requestData.put("deviceFingerprint", deviceFingerprint);
                    requestData.put("deviceInfo", deviceInfo.toJSON());
                    
                    // 发送请求
                    String response = sendRequest("/api/v1/channel-stats", requestData);
                    JSONObject jsonResponse = new JSONObject(response);
                    
                    if (jsonResponse.getInt("code") != 0) {
                        throw new Exception(jsonResponse.getString("message"));
                    }
                    
                    if (callback != null) {
                        callback.onSuccess(jsonResponse.getJSONObject("data"));
                    }
                    
                } catch (Exception e) {
                    log("Failed to get channel stats: " + e.getMessage());
                    
                    // 返回默认数据
                    JSONObject defaultStats = new JSONObject();
                    try {
                        defaultStats.put("totalInstalls", 0);
                        defaultStats.put("channelStats", new org.json.JSONArray());
                        defaultStats.put("conversionRate", 0);
                    } catch (JSONException je) {
                        // 忽略
                    }
                    
                    if (callback != null) {
                        callback.onSuccess(defaultStats);
                    }
                }
            }
        });
    }
    
    // 私有方法
    
    private DeviceInfo getDeviceInfo() {
        DeviceInfo info = new DeviceInfo();
        
        try {
            // 基本信息
            info.brand = Build.BRAND;
            info.model = Build.MODEL;
            info.device = Build.DEVICE;
            info.product = Build.PRODUCT;
            info.manufacturer = Build.MANUFACTURER;
            info.androidVersion = Build.VERSION.RELEASE;
            info.sdkVersion = Build.VERSION.SDK_INT;
            
            // 屏幕信息
            WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
            Display display = wm.getDefaultDisplay();
            DisplayMetrics metrics = new DisplayMetrics();
            display.getMetrics(metrics);
            
            info.screenWidth = metrics.widthPixels;
            info.screenHeight = metrics.heightPixels;
            info.density = metrics.density;
            info.screenResolution = info.screenWidth + "x" + info.screenHeight;
            
            // 语言和地区
            info.language = context.getResources().getConfiguration().locale.getLanguage();
            info.country = context.getResources().getConfiguration().locale.getCountry();
            info.timezone = java.util.TimeZone.getDefault().getID();
            
            // 设备ID
            info.deviceId = Settings.Secure.getString(context.getContentResolver(), Settings.Secure.ANDROID_ID);
            if (info.deviceId == null || info.deviceId.isEmpty()) {
                info.deviceId = generateUUID();
            }
            
            // 应用信息
            PackageManager pm = context.getPackageManager();
            PackageInfo packageInfo = pm.getPackageInfo(context.getPackageName(), 0);
            ApplicationInfo appInfo = pm.getApplicationInfo(context.getPackageName(), 0);
            
            info.packageName = context.getPackageName();
            info.appVersion = packageInfo.versionName;
            info.appName = pm.getApplicationLabel(appInfo).toString();
            
            // 检测模拟器
            info.isEmulator = detectEmulator();
            
            // 检测Root
            info.isRooted = detectRoot();
            
        } catch (Exception e) {
            log("Failed to get device info: " + e.getMessage());
        }
        
        return info;
    }
    
    private String generateDeviceFingerprint() {
        try {
            StringBuilder sb = new StringBuilder();
            sb.append(deviceInfo.brand);
            sb.append("_");
            sb.append(deviceInfo.model);
            sb.append("_");
            sb.append(deviceInfo.system);
            sb.append("_");
            sb.append(deviceInfo.screenResolution);
            sb.append("_");
            sb.append(deviceInfo.language);
            sb.append("_");
            sb.append(deviceInfo.timezone);
            sb.append("_");
            sb.append(deviceInfo.deviceId);
            
            return hashString(sb.toString());
        } catch (Exception e) {
            return generateUUID();
        }
    }
    
    private boolean detectEmulator() {
        return Build.FINGERPRINT.startsWith("generic") ||
               Build.FINGERPRINT.startsWith("unknown") ||
               Build.MODEL.contains("google_sdk") ||
               Build.MODEL.contains("Emulator") ||
               Build.MODEL.contains("Android SDK built for x86") ||
               Build.MANUFACTURER.contains("Genymotion") ||
               Build.BRAND.startsWith("generic") && Build.DEVICE.startsWith("generic") ||
               "google_sdk".equals(Build.PRODUCT);
    }
    
    private boolean detectRoot() {
        String buildTags = Build.TAGS;
        if (buildTags != null && buildTags.contains("test-keys")) {
            return true;
        }
        
        try {
            Process process = Runtime.getRuntime().exec("su");
            process.waitFor();
            return true;
        } catch (Exception e) {
            return false;
        }
    }
    
    private String sendRequest(String endpoint, JSONObject data) throws Exception {
        URL url = new URL(config.apiUrl + endpoint);
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        
        try {
            connection.setRequestMethod("POST");
            connection.setRequestProperty("Content-Type", "application/json");
            connection.setRequestProperty("X-API-Key", config.apiKey);
            connection.setRequestProperty("X-Session-ID", sessionId);
            connection.setRequestProperty("X-Fingerprint", deviceFingerprint);
            connection.setRequestProperty("X-SDK-Version", SDK_VERSION);
            connection.setRequestProperty("X-Platform", "android");
            connection.setConnectTimeout(config.timeout);
            connection.setReadTimeout(config.timeout);
            connection.setDoOutput(true);
            
            // 发送数据
            String jsonData = data.toString();
            if (config.enableCompression) {
                // 这里可以添加压缩逻辑
            }
            
            connection.getOutputStream().write(jsonData.getBytes("UTF-8"));
            
            // 读取响应
            int responseCode = connection.getResponseCode();
            BufferedReader reader;
            
            if (responseCode == HttpURLConnection.HTTP_OK) {
                reader = new BufferedReader(new InputStreamReader(connection.getInputStream()));
            } else {
                reader = new BufferedReader(new InputStreamReader(connection.getErrorStream()));
            }
            
            StringBuilder response = new StringBuilder();
            String line;
            while ((line = reader.readLine()) != null) {
                response.append(line);
            }
            reader.close();
            
            if (responseCode != HttpURLConnection.HTTP_OK) {
                throw new Exception("HTTP " + responseCode + ": " + response.toString());
            }
            
            return response.toString();
            
        } finally {
            connection.disconnect();
        }
    }
    
    private String getCache(String key) {
        if (!config.enableCache) return null;
        
        String cached = prefs.getString(key, null);
        if (cached != null) {
            long timestamp = prefs.getLong(key + "_timestamp", 0);
            if (System.currentTimeMillis() - timestamp < config.cacheTimeout) {
                return cached;
            }
        }
        return null;
    }
    
    private void setCache(String key, String value, long timeout) {
        if (!config.enableCache) return;
        
        SharedPreferences.Editor editor = prefs.edit();
        editor.putString(key, value);
        editor.putLong(key + "_timestamp", System.currentTimeMillis());
        editor.apply();
    }
    
    private InstallParams parseInstallParams(String json) throws JSONException {
        JSONObject jsonObject = new JSONObject(json);
        InstallParams params = new InstallParams();
        params.inviter = jsonObject.optString("inviter", null);
        params.channel = jsonObject.optString("channel", null);
        params.attributionType = jsonObject.optString("attributionType", "organic");
        params.confidence = jsonObject.optDouble("confidence", 0.0);
        params.timestamp = jsonObject.optLong("timestamp", System.currentTimeMillis());
        return params;
    }
    
    private Map<String, String> jsonToMap(JSONObject json) throws JSONException {
        Map<String, String> map = new HashMap<>();
        java.util.Iterator<String> keys = json.keys();
        while (keys.hasNext()) {
            String key = keys.next();
            map.put(key, json.getString(key));
        }
        return map;
    }
    
    private String generateUUID() {
        return UUID.randomUUID().toString();
    }
    
    private String hashString(String input) {
        try {
            java.security.MessageDigest md = java.security.MessageDigest.getInstance("MD5");
            byte[] digest = md.digest(input.getBytes());
            StringBuilder sb = new StringBuilder();
            for (byte b : digest) {
                sb.append(String.format("%02x", b));
            }
            return sb.toString();
        } catch (Exception e) {
            return String.valueOf(input.hashCode());
        }
    }
    
    private String getDefaultStartDate() {
        long thirtyDaysAgo = System.currentTimeMillis() - (30L * 24 * 60 * 60 * 1000);
        return new java.text.SimpleDateFormat("yyyy-MM-dd").format(new java.util.Date(thirtyDaysAgo));
    }
    
    private String getDefaultEndDate() {
        return new java.text.SimpleDateFormat("yyyy-MM-dd").format(new java.util.Date());
    }
    
    private void log(String message) {
        if (config.debug) {
            android.util.Log.d(TAG, message);
        }
    }
    
    /**
     * 获取版本信息
     */
    public String getVersion() {
        return SDK_VERSION;
    }
    
    /**
     * 获取调试信息
     */
    public JSONObject getDebugInfo() throws JSONException {
        JSONObject debugInfo = new JSONObject();
        debugInfo.put("version", getVersion());
        debugInfo.put("isInitialized", isInitialized);
        debugInfo.put("deviceFingerprint", deviceFingerprint);
        debugInfo.put("sessionId", sessionId);
        debugInfo.put("deviceInfo", deviceInfo.toJSON());
        debugInfo.put("config", config.toString());
        return debugInfo;
    }
}